package com.xiayuxuanmin.weixinpay.utils;
import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.SimpleHttpConnectionManager;
import org.apache.commons.httpclient.methods.GetMethod;
import org.apache.commons.httpclient.methods.PostMethod;
import org.apache.commons.httpclient.params.HttpMethodParams;
import org.apache.log4j.Logger;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.net.URL;
import java.net.URLConnection;
import java.nio.charset.StandardCharsets;
import java.util.Date;
import java.util.Map;
/**
 * Http工具类,用于发起网络请求
 * 为系统提供通用Http访问操作方法
 * 调用外部的接口，通过http方式调用
 * @Author xiayuxuanmin
 * @Date 2019/8/3
 * @Description
 */

public class HttpUtil {
    private static Logger log = Logger.getLogger("wapshop_log");

    private final static int CONNECT_TIMEOUT = 5000; // in milliseconds
    private final static String DEFAULT_ENCODING = "UTF-8";

    /**
     * 发送post请求
     * @param urlStr 请求url
     * @param data 把所有的请求参数转化为xml格式的string数据
     *  这个格式是微信需要的数据格式:
     *  格式为:"<xml><appid><![CDATA[123456]]></appid></xml>"
     * @return
     */
    public static String postData(String urlStr, String data) {
        return postData(urlStr, data, null);
    }

    /**
     * 发送post请求
     * @param urlStr 请求url
     * @param data  微信需要的请求参数转化为xml格式的string数据
     *  这个格式是微信需要的数据格式:
     *  格式为:"<xml><appid><![CDATA[123456]]></appid></xml>"
     * @param contentType 请求的contentType类型
     * @return
     */
    public static String postData(String urlStr, String data, String contentType) {
        BufferedReader reader = null;
        OutputStreamWriter writer = null ;
        try {
            //通过在 URL 上调用 openConnection 方法创建连接对象
            URL url = new URL(urlStr);
            // 通过URL对象构造URLConnection对象
            URLConnection conn = url.openConnection();

            /*这里调用openConnection后,调不调用connect后,程序运行结果一样
            * 文档上说:
            * 通过在 URL 上调用 openConnection 方法创建连接对象,操作设置参数和一般请求属性。
            * 使用 connect 方法建立到远程对象的实际连接。 远程对象变为可用。远程对象的头字段和内容变为可访问。
            * 不是很懂,到底调用connect与不调用的 区别...*/
            //连接到URL
            //con.connect();

            //输出相关的信息
//            System.out.println(" Content Type: " + conn.getContentType());
//            System.out.println(" Content Encoding: " + conn.getContentEncoding());
//            System.out.println(" Content Length: " + conn.getContentLength());
//            System.out.println(" Date: " + new Date(conn.getDate()));
//            System.out.println(" Last Modified: " + new Date(conn.getLastModified()));
//            System.out.println(" Expiration: " + new Date(conn.getExpiration()));

            //处理设置参数和一般请求属性
            //设置参数
            //可以根据请求的需要设置参数
            conn.setDoOutput(true);
            conn.setConnectTimeout(CONNECT_TIMEOUT);
            conn.setReadTimeout(CONNECT_TIMEOUT);

            if (contentType != null){
                //2.2请求属性
                //设置通用的请求属性 更多的头字段信息可以查阅HTTP协议
                conn.setRequestProperty("content-type", contentType);
            }

            //通过writer设置请求正文 即要提交的数据
            writer = new OutputStreamWriter(conn.getOutputStream(), DEFAULT_ENCODING);
            if (data == null) {
                writer.write("");
            } else {
                writer.write(data);
            }
            writer.flush();

            //获取响应正文
            reader = new BufferedReader(new InputStreamReader(conn.getInputStream(), DEFAULT_ENCODING));
            StringBuilder sb = new StringBuilder();
            String line = null;
            while ((line = reader.readLine()) != null) {
                sb.append(line);
                sb.append("\r\n");
            }
            return sb.toString();
        } catch (IOException e) {
            e.printStackTrace();
            log.error(e);
        } finally {
            try {
                if (reader != null){
                    reader.close();
                }
                if(writer != null){
                    writer.close();
                }
            } catch (IOException e) {
                log.error(e);
            }
        }
        return null;
    }

    /**
     * 处理post请求
     * @param url 请求url
     * @param map 请求的map格式的参数
     * @return
     */
    public static String postHttp(String url, Map<String, String> map) {
        HttpClient httpclient = null;
        PostMethod post = null;
        SimpleHttpConnectionManager simpleHttpConnectionManager = null;
        String info = null;
        try {
            httpclient = new HttpClient();
            post = new PostMethod(url);
            // 设置编码方式
            post.getParams().setParameter(HttpMethodParams.HTTP_CONTENT_CHARSET, "UTF-8");
            httpclient.getHttpConnectionManager().getParams().setConnectionTimeout(30000);
            httpclient.getHttpConnectionManager().getParams().setSoTimeout(30000);
            // 添加参数
            if (map != null) {
                for (Map.Entry<String, String> entry : map.entrySet()) {
                    String key = entry.getKey();
                    post.addParameter(key, entry.getValue());
                }
            }
            // 执行
            httpclient.executeMethod(post);
            // 接口返回信息
            info = new String(post.getResponseBody(), "UTF-8");
        } catch (Exception e) {
            log.error(e);
        } finally {
            // 关闭连接，释放资源
            if (post != null) {
                post.releaseConnection();
            }
            if (httpclient != null) {
                simpleHttpConnectionManager = ((SimpleHttpConnectionManager) httpclient.getHttpConnectionManager());
                if (simpleHttpConnectionManager != null) {
                    simpleHttpConnectionManager.shutdown();
                }
            }

        }
        return info;
    }

    /**
     * 处理get请求
     * @param url
     *  请求地址 如
     *  http://localhost:9090/base_rpc/basicData/getInvoice?t=1507513445960&invoiceId=039D906D07C74306B635DD89F87584CD&token=bd302857fbd4a01af7401fe229d43918
     * @return
     */
    public static String getHttp(String url) {
        HttpClient httpClient = null;
        GetMethod get = null;
        SimpleHttpConnectionManager simpleHttpConnectionManager = null;
        String info = null;

        try {
            httpClient = new HttpClient();
            get = new GetMethod(url);
            // 执行
            httpClient.executeMethod(get);
            // 接口返回信息
            info = new String(get.getResponseBody(), StandardCharsets.UTF_8);
            log.info("接口【" + url + "】 返回:" + info);
        } catch (Exception e) {
            log.info("调用接口【" + url + "】  出错:" + e);
            return null;
        } finally {
            if (get != null) {
                get.releaseConnection();
            }
            if (httpClient != null) {
                simpleHttpConnectionManager = (SimpleHttpConnectionManager) httpClient.getHttpConnectionManager();
                if (simpleHttpConnectionManager != null) {
                    simpleHttpConnectionManager.shutdown();
                }
            }
        }
        return info;
    }

}
